﻿using System;
using System.Collections.Generic;
using System.Linq;
using Autodesk.Revit.DB;
using Autodesk.Revit.DB.Architecture;
using YJKRevitKernel.GeometryUtility;

namespace YJKRevitDimensionText.VerticalAutoDim.GeoModel
{
	internal class RailingGeo : IPlanarGeo
	{
		public RailingGeo(Element railing, Plane pl, Transform transformWcs2Ecs)
		{
			this.Railing = (railing as Railing);
			this.plane = pl;
			this.TransformWcs2Ecs = transformWcs2Ecs;
		}

		public Plane Plane
		{
			get
			{
				return this.plane;
			}
		}

		public Element Element
		{
			get
			{
				return this.Railing;
			}
		}

		public int Weight
		{
			get
			{
				return 6;
			}
		}

		public XYZ Max2DPointECS
		{
			get
			{
				return this.MaxPointEcs;
			}
		}

		public XYZ Min2DPointECS
		{
			get
			{
				return this.MinPointEcs;
			}
		}

		public XYZ Max3DPointWCS
		{
			get
			{
				return this.MaxPointWcs;
			}
		}

		public XYZ Min3DPointWCS
		{
			get
			{
				return this.MinPointWcs;
			}
		}

		public double TopElev
		{
			get
			{
				return this.Max3DPointWCS.Z;
			}
		}

		public double BottomElev
		{
			get
			{
				return this.Min3DPointWCS.Z;
			}
		}

		public double Width
		{
			get
			{
				return this.width;
			}
		}

		public double Dist2Plane { get; private set; }

		public double Distance2Plane
		{
			get
			{
				throw new NotImplementedException();
			}
		}

		public bool Init()
		{
			List<Solid> allSolid = GeometryUtilityMethod.GetAllSolid(this.Element.get_Geometry(new Options()), null);
			if (allSolid.Count == 0)
			{
				return false;
			}
			List<XYZ> list = new List<XYZ>();
			foreach (Solid solid in allSolid)
			{
				foreach (object obj in ExtrusionAnalyzer.Create(solid, this.plane, this.plane.Normal).GetExtrusionBase().EdgeLoops)
				{
					foreach (object obj2 in ((EdgeArray)obj))
					{
						Edge edge = (Edge)obj2;
						XYZ endPoint = edge.AsCurve().GetEndPoint(0);
						XYZ endPoint2 = edge.AsCurve().GetEndPoint(1);
						list.Add(this.TransformWcs2Ecs.OfPoint(endPoint));
						list.Add(this.TransformWcs2Ecs.OfPoint(endPoint2));
					}
				}
			}
			if (EnumerableExternsion.IsEmpty<XYZ>(list))
			{
				return false;
			}
			List<XYZ> source = (from e in list
			orderby e.X
			select e).ToList<XYZ>();
			List<XYZ> source2 = (from e in list
			orderby e.Y
			select e).ToList<XYZ>();
			XYZ xyz = source.First<XYZ>();
			double z = xyz.Z;
			double y = source2.First<XYZ>().Y;
			double y2 = source2.Last<XYZ>().Y;
			double x = xyz.X;
			double x2 = source.Last<XYZ>().X;
			this.MinPointEcs = new XYZ(x, y, z);
			this.width = x2 - x;
			double num = y2 - y;
			this.MaxPointEcs = this.MinPointEcs + this.plane.XVec * this.width;
			this.MaxPointEcs += this.plane.YVec * num;
			this.MinPointWcs = this.TransformWcs2Ecs.Inverse.OfPoint(this.MinPointEcs);
			this.MaxPointWcs = this.TransformWcs2Ecs.Inverse.OfPoint(this.MaxPointEcs);
			return true;
		}

		private readonly Transform TransformWcs2Ecs;

		private readonly Railing Railing;

		private readonly Plane plane;

		private double width;

		private XYZ MinPointEcs;

		private XYZ MaxPointEcs;

		private XYZ MinPointWcs;

		private XYZ MaxPointWcs;
	}
}
